#include "softkeyboard.h"
#include "view/handwidget.h"
#include <QLabel>
#include <QDebug>
#include <QScreen>
#include <QGuiApplication>
#include <QFont>
#include <QApplication>
#include <QDesktopWidget>
#include "myskin.h"
#include "view/num_keyboard.h"
#include "view/en_keyboard.h"
#include "view/punctuationsview.h"

SoftKeyboard::SoftKeyboard(QWidget *parent) :
    QWidget(parent)
{
    this->setWindowFlags(Qt::FramelessWindowHint);//无边框
    this->setMoveEnabled(false);     //设置界面是否可拖动



    chineseServer.init();

    /* 实例化相关控件 */
    initCandidate();
    init();
    initKeyboard();


    letterLabel = new MYMovableLabel(this);
    letterLabel->setMinimumWidth(30);
    QFont font = letterLabel->font();
    font.setPixelSize(20);
    font.setUnderline(true);
    letterLabel->setFont(font);



    QHBoxLayout *globalHLayout = new QHBoxLayout(this);
    QVBoxLayout *keyVLayout = new QVBoxLayout();

    //添加布局
    //keyVLayout->addWidget(letterLabel);
    //创建一个窗口将候选框和退出按钮以垂直布局放进去
    QWidget *qw = new QWidget;
    QHBoxLayout *qh = new QHBoxLayout;
    qh->addWidget(translateHDragableWidget,19);
    qh->addStretch(1);
    qw->setLayout(qh);

    keyVLayout->addWidget(qw);
    keyVLayout->addWidget(sKey);
    keyVLayout->setSpacing(0);
    keyVLayout->setMargin(0);


    //添加布局
    globalHLayout->addLayout(globalVLayout);
    globalHLayout->addLayout(keyVLayout);
    globalHLayout->setSpacing(0);   //内边距设置为0
//    globalHLayout->setMargin(0);    //外边距设置为0
    globalHLayout->setContentsMargins(10, 10, 0, 0);

    connect(translateHView, &MyHDragableTranslateView::clicked, this, &SoftKeyboard::userSelectChinese);
    connect(translateVView, &MyVDragableTranslateView::clicked, this, &SoftKeyboard::userSelectChinese);

}

/**
 * @brief SoftKeyboard::userSelectChinese
 * @param text
 * @param index
 * 拼音输入时点击候选词的处理方法
 */
void SoftKeyboard::userSelectChinese(const QString &text, int index)
{   
    QString showText;
    QList<XYTranslateItem *> lists = XYInputSearchInterface::getInstance()->completeInput(text, index, showText);
    letterLabel->setText(showText);

    if(lists.isEmpty()){        //点击候选词后无剩余候选字母
        //这里完成输入
        textShow->setText(textShow->text().append(alreadySelectTranslates.join("") + text));  //将数据发送出去
        clear_history();        //清空数据
        switchPage(1);
    }
    else    //如果还剩候选字母则留着等着再次处理
    {
        alreadySelectTranslates.append(text);
        translateHView->dataStrings.clear();
        foreach(XYTranslateItem *temp, lists){
            translateHView->dataStrings.append(temp->msTranslate);
        }
        translateHView->move(0,0);
        translateHView->update();
        if(sKey->currentIndex() == 4){
            translateVView->dataStrings = translateHView->dataStrings;
            translateVView->move(0,0);
            translateVView->update();
        }
    }
}

/**
 * @brief SoftKeyboard::a2zkey_clicked
 * @param unicode
 * @param key
 * @return
 * 添加候选字母
 */
bool SoftKeyboard::a2zkey_clicked(int unicode, int key)
{
    alreadyInputLetters.append(QChar(unicode).toLower());
    search_begin(XYInputSearchInterface::getInstance()->searchTranslates(alreadyInputLetters));
    return true;
}

/**
 * @brief SoftKeyboard::search_begin
 * @param lists
 * 根据候选字母映射出候选词
 */
void SoftKeyboard::search_begin(QList<XYTranslateItem *> lists)
{
    translateHView->dataStrings.clear();
    foreach (XYTranslateItem *temp, lists) {
        translateHView->dataStrings.append(temp->msTranslate);
    }
    letterLabel->setText(XYInputSearchInterface::getInstance()->getCurLetters());
    translateHView->update();
}

MyDragableWidget * SoftKeyboard::getHDragableWidget()
{
    return translateHDragableWidget;
}
MyHDragableTranslateView * SoftKeyboard::gettranslateHView()
{
    return translateHView;
}

/**
 * @brief SoftKeyboard::clear_history
 * 重置候选框数据
 */
void SoftKeyboard::clear_history()
{
    letterLabel->clear();
    alreadyInputLetters.clear();
    alreadySelectTranslates.clear();
    translateVView->dataStrings.clear();
    translateVView->update();
    translateHView->dataStrings.clear();
    translateHView->move(0,0);
    translateHView->update();
    //switchPage(previous);
    //sKey->setCurrentIndex(1);
    translateVDragableWidget->setHidden(true);
    XYInputSearchInterface::getInstance()->resetSearch();
}


void SoftKeyboard::paintEvent(QPaintEvent *e)
{
    QPainter painter(this);
    painter.setRenderHint(QPainter::Antialiasing);
    //按钮的宽度
    int btn_w = 60;
    QPainterPath path;

    //右上角三角形
    int w = 20;     //三角形宽度
    int h = 10;     //三角形高度
    int startX = width()-(btn_w-(btn_w-w)/2);
    int startY = (btn_w-h)/2;
    path.moveTo(startX, startY);
    path.lineTo(startX + w/2, startY + h);
    path.lineTo(startX + w, startY);

    painter.setPen(MYSKIN->borderPen);
    painter.setBrush(MYSKIN->topColor);

    //这里画出候选框矩形
    painter.drawRect(rect().x()+100, rect().y(), rect().width(), letterLabel->height()+25);
    //三角按钮矩形
    triangleBtnRect = QRect(rect().width()-btn_w, 0, btn_w, letterLabel->height() + 25);

    //三角按钮按下和未按下是不同的样式
    if(triangleBtnPressed)
    {
        painter.setBrush(MYSKIN->trianglePressedBKColor);
        painter.setPen(painter.brush().color());
        painter.drawRect(triangleBtnRect);
        painter.setPen(MYSKIN->trianglePen);
        painter.drawPath(path);
    }else {
        painter.setBrush(MYSKIN->topColor);
        painter.setPen(MYSKIN->trianglePen);
        painter.drawPath(path);
    }

    painter.setPen(MYSKIN->borderPen);
    if(sKey->currentIndex() == 4 || sKey->currentIndex() == 3){
        painter.setBrush(MYSKIN->bottomColor1);
    }else {
        painter.setBrush(MYSKIN->bottomColor2);
    }

    if(sKey->currentIndex() != 4){
        painter.setPen(MYSKIN->borderPen);
        //当显示按钮时的底部颜色
        painter.setBrush(MYSKIN->bottomColor2);
    }

    //将字母显示控件移动到指定位置，目前为固定值，等后期修改为百分比值
    letterLabel->move(100,0);


    painter.drawRect(rect().x()+100,
                            rect().y() + letterLabel->height() + 27,
                            rect().width(),
                            rect().height()-(letterLabel->height() + 27));

}


void SoftKeyboard::triangleBtnClickedOP()
{
    if(translateHView->dataStrings.isEmpty())
    {
//        qDebug() << "退出成功!";
        qApp->quit();

    }else{
        if(sKey->currentIndex() != 4){
            translateVView->dataStrings = translateHView->dataStrings;
            translateVView->move(0,0);
            //qDebug() << translateVView->dataStrings.size() << translateHView->dataStrings.size();
            translateVView->update();
            switchPage(4);
            //sKey->setCurrentIndex(4);
        }
        else {
            switchPage(previous);
            //sKey->setCurrentIndex(previous);
        }
    }
}


/**
 * @brief SoftKeyboard::showEvent
 * @param event
 * 重写showEvent函数
 */
void SoftKeyboard::showEvent(QShowEvent* event)
{
    QWidget::showEvent(event);
    switchPage(1);
    this->move((applicationRect.width()-kSizeW)/2, applicationRect.height()-kSizeH-200);       //移动窗口位置
//    qDebug() << this->pos();
}




/**
 * @brief SoftKeyboard::init
 * 窗口初始化函数
 */
void SoftKeyboard::init(){

    applicationRect = QGuiApplication::screens().at(0)->geometry();     //获取显示屏像素


    int w = applicationRect.width();            //显示屏的宽
    int h = applicationRect.height();           //显示屏的高

    if (w < winSizeW){
        winSizeW = w*0.6;               //根据显示屏大小设置顶层窗口的默认大小
    }
    winSizeH = winSizeW * 0.6;          //设置顶层窗口的默认高度
    if (h * 0.8 < winSizeH){
        winSizeH = h;
    }

    a = winSizeW*1.0/(800+50);    //根据界面大小等比例变换窗口大小
}

/**
 * @brief SoftKeyboard::initKeyType
 * 初始化键盘相关控件
 */
void SoftKeyboard::initKeyboard()
{
    sKey = new QStackedWidget();
    globalVLayout = new QVBoxLayout();

    //实例化键盘选项控件
    keyTypeTab[0] = new QLabel("数字", this);
    keyTypeTab[1] = new QLabel("拼音", this);
    keyTypeTab[2] = new QLabel("手写", this);
    keyTypeTab[3] = new QLabel("符", this);

    //实例化键盘对象
    keyTypePage[0] = new num_keyboard(this);
    keyTypePage[1] = new EN_KeyBoard(this);
    keyTypePage[2] = new HandWidget(this);
    keyTypePage[3] = new PunctuationsView(this);
    keyTypePage[4] = translateVDragableWidget;

    //创建字体对象用来设置控件的字体和大小
    QFont font("Microsoft YaHei", 18, QFont::DemiBold);

    globalVLayout->addStretch(3);
    //将键盘及键盘选项添加进相关Layout中，并设置键盘选项控件的样式
    for (int i = 0; i < 4; i++) {
        keyTypeTab[i]->installEventFilter(this);
        keyTypeTab[i]->setFont(font);
        keyTypeTab[i]->setAlignment(Qt::AlignCenter);
        keyTypeTab[i]->setMargin(10);           //设置外边距为10
        //keyTypeTab[i]->setFixedSize(keyTypeTab[i]->size());
        globalVLayout->addWidget(keyTypeTab[i]);
        sKey->addWidget(keyTypePage[i]);
        globalVLayout->addStretch(1);
    }
    sKey->addWidget(keyTypePage[4]);
    globalVLayout->setMargin(10);
}

/**
 * @brief SoftKeyboard::initCandidate
 * 初始化候选框相关控件
 */
void SoftKeyboard::initCandidate()
{
    //初始化 三角按钮未按下
    triangleBtnPressed = false;
    connect(this, &SoftKeyboard::triangleBtnClicked, this, &SoftKeyboard::triangleBtnClickedOP);

    //初始化水平候选词拖拽控件
    translateHDragableWidget = new MyDragableWidget(translateHView,
                                                    MyDragableWidget::HORIZONTAL1,this);
    translateHDragableWidget->setMinimumHeight(30);
    translateHDragableWidget->setMouseSensitivity(5);


    translateVView->setUnitMinHeight(40);
    translateVView->setUnitMinWidth(50);
    //初始化垂直候选词拖拽控件
    translateVDragableWidget = new MyDragableWidget(translateVView,MyDragableWidget::VERTICAL1);
    translateVDragableWidget->setMouseSensitivity(5);
    translateVDragableWidget->setHidden(true);
}

/**
 * @brief SoftKeyboard::fillCandidateText
 * @param strList 待填充的文本列表
 * 填充候选框文本
 */
void SoftKeyboard::fillCandidateText(QStringList strList){

    translateHView->dataStrings.clear();        //清空候选词
    translateHView->dataStrings.append(strList);    //填充候选词
    translateHView->move(0,0);
    translateHView->update();
}

/**
 * @brief SoftKeyboard::switchPage
 * @param type 需要切换的布局
 * 切换布局，更新窗口大小
 *
 */
void SoftKeyboard::switchPage(int type)
{
    //如需要切换的键盘和当前显示的键盘是同一个则直接不做处理，放置多次重复点击
    if (sKey->currentIndex() == type){
        return;
    }
    switch (type) {
        case 0:
            kSizeW = 500 * a;
            kSizeH = 350 * a;
            tSizeW = 100 * a;
            break;
        case 1:
            kSizeW = 800 * a;
            kSizeH = 350 * a;
            tSizeW = 100 * a;
        break;
        case 2:
            kSizeW = 550 * a;
            kSizeH = 350 * a;
            tSizeW = 100 * a;
        break;
        case 3:
            kSizeW = 550 * a;
            kSizeH = 350 * a;
            tSizeW = 100 * a;
        break;
        case 4:
            break;
        default:
            return;
    }

    //切换键盘是将手写界面初始化为汉字识别
    MyPushButton::abc123 = false;

    previous = sKey->currentIndex();
    for (int i = 0; i < 4; i++) {
         keyTypeTab[i]->setStyleSheet("background-color:transparent;");
    }
    if (type < 4){
        keyTypeTab[type]->setStyleSheet("background-color:white;");
    }

    sKey->setCurrentIndex(type);        //更新QStackedWidget栈布局内容
    sKey->resize(kSizeW,kSizeH);        //更改QStackedWidget栈布局大小
    this->resize(kSizeW+tSizeW, kSizeH+50);    //更新窗口大小
    sKey->setMinimumHeight(kSizeH);
    this->setMaximumHeight(kSizeH+50);
//    this->move((applicationRect.width()-kSizeW+tSizeW)/2, applicationRect.height()-kSizeH-100);   //移动窗口位置

}

void SoftKeyboard::getTextByHand(CharacterEntity character)
{
    QStringList strs = chineseServer.getChineseByHand(character, candidateWordNum);
    fillCandidateText(strs);
}

/* 响应槽函数 */

/* 特殊按键响应槽 */

/**
 * @brief deleteSlot
 * 删除按钮被点击时若拼音字母栏有字符则删除拼音字母栏的最后一个字母，否则删除输出框的最后一个字符
 */
void SoftKeyboard::deleteSlot()
{
    if (!alreadyInputLetters.isEmpty()){
        qDebug() << "删除候选字母";
        alreadyInputLetters = alreadyInputLetters.mid(0, alreadyInputLetters.size()-1);
        search_begin(XYInputSearchInterface::getInstance()->searchTranslates(alreadyInputLetters));
    } else{
        if(!translateHView->dataStrings.isEmpty()){
            clear_history();
        }
        else if (textShow != nullptr && !textShow->text().isEmpty()) {
            qDebug() << "删除文本框数据";
            textShow->setText(textShow->text().mid(0, textShow->text().size()-1));
        }
    }

}

void SoftKeyboard::enterSlot()
{

    if(letterLabel->text().isEmpty())
    {
        addCandidateCharacterText("\n");
        return;
    }
    else if(translateHView->dataStrings.size() > 0){
        addCandidateCharacterText(alreadyInputLetters);
    }
    clear_history();

}

void SoftKeyboard::spaceSlot()
{
    if(letterLabel->text().isEmpty())
    {
        addCandidateCharacterText(" ");
        return;
    }
    else if(translateHView->dataStrings.size() > 0){
        userSelectChinese(translateHView->dataStrings.at(0),0);
    }
}

/**
 * @brief SoftKeyboard::finishSlot
 * 当完成输入按钮被点击时关闭输入框
 */
void SoftKeyboard::finishSlot()
{
    this->close();
}

/* 重写事件 */

/**
 * @brief SoftKeyboard::eventFilter
 * @param obj
 * @param event
 * @return 重写eventFilter事件，获取指定控件（键盘布局选项按钮）的点击事件
 */
bool SoftKeyboard::eventFilter(QObject *obj, QEvent *event)
{
    int flag = 0;
    int type;

    for (int i = 0; i < 4; i++) {
        if (obj == keyTypeTab[i]){
            flag = 1;
            type = i;
        }
    }

    if (flag)//指定的某个QLabel控件被点击
         {
             if (event->type() == QEvent::MouseButtonPress) //鼠标点击
             {
                 QMouseEvent *mouseEvent = static_cast<QMouseEvent*>(event); // 事件转换

                 if(mouseEvent->button() == Qt::LeftButton)
                 {
                     switchPage(type);
                     return true;
                 }
                 else
                 {
                     return false;
                 }
             }
             else
             {
                 return false;
             }
         }
         else
         {
             return QWidget::eventFilter(obj, event);
         }

    return QWidget::eventFilter(obj, event);
}

/**
 * @brief SoftKeyboard::setMoveEnabled
 * @param moveEnabled
 * 设置是否可拖动
 */
void SoftKeyboard::setMoveEnabled(bool moveEnabled) {
    isMoveEnabled = moveEnabled;
}

/**
 * @brief SoftKeyboard::mousePressEvent
 * @param event
 * 重写鼠标按下键，获取鼠标左键按下时的全局位置，将窗口的可移动标志设置为true
 */
void SoftKeyboard::mousePressEvent(QMouseEvent *event) {
    if (event->button() == Qt::LeftButton)//左键按下
    {
        isMousePress = true;
        cursorGlobalPos = event->globalPos();//获取鼠标按下时的全局位置
    }
    if(event->button() == Qt::LeftButton && triangleBtnRect.contains(event->pos()))
    {
        triangleBtnPressed = true;
        update();
    }
}

/**
 * @brief SoftKeyboard::mouseMoveEvent
 * @param event
 * 重写鼠标移动事件，使窗口跟着鼠标移动
 */
void SoftKeyboard::mouseMoveEvent(QMouseEvent *event) {
    //不可以用event.button()==Qt::LeftButton来判断，因为在鼠标移动事件里该方法一直返回Qt::NoButton
    if (event->buttons() & Qt::LeftButton && isMousePress && isMoveEnabled) {
        //qDebug()<<"mouse move:"<<event->globalPos();
        QPoint position = this->pos() + event->globalPos() - cursorGlobalPos;
        move(position.x(), position.y());
        cursorGlobalPos = event->globalPos();
    }
}

/**
 * @brief SoftKeyboard::mouseReleaseEvent
 * @param event
 * 重写鼠标抬起（释放）事件，将窗口的可移动标志设置为false
 */
void SoftKeyboard::mouseReleaseEvent(QMouseEvent *event) {
    if (event->button() == Qt::LeftButton)//左键释放
    {
        isMousePress = false;
    }
    if(event->button() == Qt::LeftButton)
    {
        if(triangleBtnPressed){
            if(triangleBtnRect.contains(event->pos()))
            {

                emit triangleBtnClicked();
            }
            update();
        }
        triangleBtnPressed = false;

    }
}

/* 给子布局的接口 */




/**
 * @brief addCandidateCharacterText
 * @param character
 * 将字符添加到输出框中
 */
void SoftKeyboard::addCandidateCharacterText(QString character)
{
    qDebug() << "输出：" << character;
    textShow->setText(textShow->text().append(character));
}

SoftKeyboard::~SoftKeyboard(){}


bool MYMovableLabel::event(QEvent *event)
{
    static QPoint lastPoint;
    static bool   pressed = false;
    if (event->type() == QEvent::MouseButtonPress)
    {
        QMouseEvent *mouse_event = static_cast<QMouseEvent *>(event);
        if (mouse_event && mouse_event->button() == Qt::LeftButton)
        {
            lastPoint = mouse_event->globalPos();
            pressed = true;
        }
        return true;
    }
    else if (event->type() == QEvent::MouseButtonRelease)
    {
        QMouseEvent *mouse_event = static_cast<QMouseEvent *>(event);
        if (mouse_event && mouse_event->button() == Qt::LeftButton)
        {
            pressed = false;
        }
        return true;
    }
    else if (event->type() == QEvent::MouseMove)
    {
        QMouseEvent *mouse_event = static_cast<QMouseEvent *>(event);
        if (parentWidget() != NULL && pressed)
        {
            QPoint movePos(parentWidget()->x() - lastPoint.x() + mouse_event->globalX(),
                           parentWidget()->y() - lastPoint.y() + mouse_event->globalY());
            if (movePos.x() >= 0
                    && movePos.x() + parentWidget()->width() <= qApp->desktop()->width()
                    && movePos.y() >= 0
                    && movePos.y() + parentWidget()->height() <= qApp->desktop()->height())
            {
                parentWidget()->move(movePos);
            }
            lastPoint = mouse_event->globalPos();
        }
        else
        {
            pressed = false;
        }
        return true;
    }
    else if (event->type() == QEvent::Enter)
    {
        setCursor(QCursor(Qt::SizeAllCursor));
    }
    return QWidget::event(event);
}
